#include "../logs/log.hpp"
#include <unistd.h>

/*日志落地方向扩展测试
    以时间为滚动单位进行写日志
*/
enum class TimeGap
{
    GAP_SECOND,
    GAP_MINUTE,
    GAP_HOUR,
    GAP_DAY
};
class RollByTimeSink : public wu::LogSink
{
public:
    RollByTimeSink(const std::string &basename, TimeGap gap_type)
        :_basename(basename)
    {
        //判断是以什么时间为滚动的
        switch (gap_type)
        {
            case (TimeGap::GAP_SECOND): _gap_size = 1; break;
            case (TimeGap::GAP_MINUTE): _gap_size = 60; break;
            case (TimeGap::GAP_HOUR): _gap_size = 3600; break;
            case (TimeGap::GAP_DAY): _gap_size = 3600 * 24; break;
            default:
                std::cout << "输出的时间类型有误" << std::endl;
                exit(-1);
        }

        //获取当前时间段
        _cur_gap = _gap_size == 1 ? wu::util::Data::getTime() : wu::util::Data::getTime() % _gap_size;

        //创建文件
        std::string filename = createFilename();
        wu::util::File::createDirectory(wu::util::File::path(filename));
        _ofs.open(filename, std::ios::binary | std::ios::app);
        assert(_ofs.is_open());//打开失败

    }

    void log(const char* data, size_t len) override
    {
        //先判断当前时间是否在同一个时间段内
        time_t cur = wu::util::Data::getTime();
        if(cur % _gap_size != _cur_gap)
        {
            _ofs.close();
            std::string filename = createFilename();
            wu::util::File::createDirectory(wu::util::File::path(filename));
            _ofs.open(filename, std::ios::binary | std::ios::app);
            assert(_ofs.is_open());//打开失败
        }
        _ofs.write(data, len);
        assert(_ofs.good());
    }
private:
    std::string createFilename() 
        {
            //先获取当前时间
            time_t t = time(nullptr);
            struct tm lt;
            localtime_r(&t, &lt);
            std::stringstream ss;
            //构建文件名
            ss << _basename;
            ss << lt.tm_year+1900;
            ss << lt.tm_mon + 1;
            ss << lt.tm_mday;
            ss << lt.tm_hour;
            ss << lt.tm_min;
            ss << lt.tm_sec;
            ss << ".log";//文件后缀
            return ss.str();
        }
private:
    std::string _basename;
    std::ofstream _ofs;
    size_t _gap_size;//时间段大小
    size_t _cur_gap;//当前是第几个时间段
};


int main()
{
    std::string name = "async-logger";
    std::unique_ptr<wu::LoggerBuilder> build(new wu::GlobalLoggerBuilder());
    build->buildLoggerName(name);
    build->buildLoggerType(wu::LoggerType::LOGGER_ASYNC);
    build->buildFormatter("[%f:%l]%m%n");
    build->buildLoggerLevel(wu::LogLevel::value::WARN);
    build->buildSink<RollByTimeSink>("./filelog/roll-", TimeGap::GAP_SECOND);//1s
    wu::Logger::ptr logger = build->build();
     
    size_t now_time = wu::util::Data::getTime();
    while(wu::util::Data::getTime() < now_time+5)
    {
        logger->fatal("滚动文件以时间为单位");
        usleep(1000);
    }
    return 0;
}